package com.surpassun.emall.interceptor;

import java.util.List;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.context.ApplicationListener;
import org.springframework.context.event.ContextRefreshedEvent;

import com.surpassun.emall.model.Category;
import com.surpassun.emall.model.Province;
import com.surpassun.emall.model.Role;
import com.surpassun.emall.model.StoreType;
import com.surpassun.emall.model.User;
import com.surpassun.emall.service.CategoryService;
import com.surpassun.emall.service.PermissionService;
import com.surpassun.emall.service.ProvinceService;
import com.surpassun.emall.service.RoleService;
import com.surpassun.emall.service.StoreTypeService;
import com.surpassun.emall.service.UserService;
import com.surpassun.emall.util.CacheUtil;
import com.surpassun.emall.util.Constants;
import com.surpassun.emall.util.ListUtil;
import com.surpassun.emall.util.PropsKeys;
import com.surpassun.emall.util.PropsUtil;
import com.surpassun.emall.util.Validator;

/**
 * Add static data into cache on application starting up in order to improve performance 
 * 
 * @author sakyrenxun@gmail.com
 *
 */
public class AppStartupAction implements ApplicationListener<ContextRefreshedEvent> {

	private Logger _log = LoggerFactory.getLogger(AppStartupAction.class);
	
	@SuppressWarnings("unchecked")
	@Override
	public void onApplicationEvent(ContextRefreshedEvent event) {
		//Add permissions
		PermissionService permissionService = event.getApplicationContext().getBean(PermissionService.class);
		permissionService.initializePermissions();
		
		//Add roles
		_log.info("Checking admin role...");
		RoleService roleService = event.getApplicationContext().getBean(RoleService.class);
		Role adminRole = roleService.addRoleAdmin();
		
		//add admin
		String adminEmailAddress = PropsUtil.getString(PropsKeys.DEFAULT_ADMIN_EMAIL_ADDRESS);
		UserService userService = event.getApplicationContext().getBean(UserService.class);
		_log.info("Checking admin user...");
		User admin = userService.getUserByEmail(adminEmailAddress);
		if (Validator.isNull(admin)) {
			_log.info("Admin doesn't exist, adding admin...");
			String adminPassword = PropsUtil.getString(PropsKeys.DEFAULT_ADMIN_PASSWORD);
			userService.add("", "Admin", "Admin", adminEmailAddress, adminPassword, "", true, null, ListUtil.fromSingleObject(adminRole));
			_log.info("User admin added with the role admin");
		}
		
		//add store type
		String[] storeTypeNames = PropsUtil.getArray(PropsKeys.ADMIN_STORE_TYPE);
		StoreTypeService storeTypeService = event.getApplicationContext().getBean(StoreTypeService.class);
		_log.info("Checking store types...");
		storeTypeService.initializeStoreTypes(storeTypeNames, null);
		
		//add category
		String[] productCategories = PropsUtil.getArray(PropsKeys.ADMIN_PRODUCT_CATEGORY);
		CategoryService categoryService = event.getApplicationContext().getBean(CategoryService.class);
		_log.info("Checking product categories...");
		categoryService.initializeCategories(productCategories, null);
		
		//Add cache
		ProvinceService provinceService = event.getApplicationContext().getBean(ProvinceService.class);
		List<Province> provinces = provinceService.getAll();
		List<StoreType> storeTypes = storeTypeService.getRootTypes();
		List<Category> categories = categoryService.getRootCategories();
		
		
		CacheUtil.getCache().put(Constants.ATTR_PROVINCES, provinces);
		_log.info((provinces != null ? provinces.size() : 0) + " provinces added to cache");
		CacheUtil.getCache().put(Constants.ATTR_STORE_TYPES, storeTypes);
		_log.info((storeTypes != null ? storeTypes.size() : 0) + " store types added to cache");
		CacheUtil.getCache().put(Constants.ATTR_CATEGORIES, categories);
		_log.info((categories != null ? categories.size() : 0) + " categories added to cache");
	}

}
